package com.rainbow.redis.plus.core.aop;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;

import com.rainbow.qps.FlowHelper;
import com.rainbow.qps.common.TimeUtil;
import com.rainbow.redis.plus.core.monitor.BlackTagService;

@Aspect
public class RedisAspect  {
	
	private Logger logger = LoggerFactory.getLogger(RedisAspect.class);
	
	@Autowired(required = false)
	private BlackTagService blackTagService;
	
	// 统计每秒，每分钟，每小时的请求总数，成功数，异常数，请求耗时
	@Autowired(required = false)
    private FlowHelper flowHelper;
	
	/**
     * 定义切入点，切入点为com.rainbow.redis.plus.core.RedisService下的所有函数
     */
    @Pointcut("execution(public * com.rainbow.redis.plus.core.RedisService.*(..))")
    public void opt(){}
    
    @Around("opt()")
    public Object doAround(ProceedingJoinPoint pjp) throws Throwable {
    	logger.info("环绕通知的目标方法名：" + pjp.getSignature().getName());
    	if (blackTagService!=null && blackTagService.isBlack()) {
			throw new Exception("此【项目名:" + blackTagService.getProjectName()  + ",实例IP:"+ blackTagService.getLocalInstanceIp() +  ",实例端口:" +blackTagService.getLocalInstancePort() + "】已经加入黑名单，无法请求redis");
		}
    	
    	try {
    		if (flowHelper == null) {
				return pjp.proceed();
			}else {
				//执行开始时间
	        	long startTime = TimeUtil.currentTimeMillis();
	        	
	            Object obj = pjp.proceed();
	            
	            //执行耗时
	            long rt = TimeUtil.currentTimeMillis() - startTime;
	            //加入成功次数
	            flowHelper.incrSuccess(rt);
	            
	            return obj;
			}
		} catch (Exception e) {
			//调用异常
			if (flowHelper == null) {
				flowHelper.incrException();
			}
            e.printStackTrace();
		}
        
        return null;
    }

}
